// AFI Summit 2026 - Integracion ePayco + Gravity Forms v4 // Endpoint correcto: https://secure.payco.co/checkout.php define( 'AFIDRO_PUBLIC_KEY', 'd4dd7d79c823f7b894d8c943f43e29e5' ); define( 'AFIDRO_CLIENTE_ID', '1581713' ); define( 'AFIDRO_TEST', false ); define( 'AFIDRO_FORM_ID', 3 ); define( 'AFIDRO_PRECIO', 500000 ); define( 'AFIDRO_IVA_PCT', 0.19 ); // IDs de campos Gravity Forms define( 'F_NOMBRE', 1 ); define( 'F_EMPRESA', 3 ); define( 'F_CARGO', 4 ); define( 'F_EMAIL', 5 ); define( 'F_TELEFONO', 6 ); define( 'F_CANTIDAD', 13 ); define( 'F_NOM_FAC', 15 ); define( 'F_NIT', 16 ); define( 'F_DIR', 17 ); define( 'F_CIUDAD', 18 ); define( 'F_EMAIL_FAC', 19 ); define( 'F_CEDULA', 20 ); // Validar cédula duplicada en Gravity Forms add_filter( 'gform_validation_3', 'afidro_validar_cedula_duplicada' ); function afidro_validar_cedula_duplicada( $validation_result ) { $form = $validation_result['form']; $cedula = rgpost( 'input_20' ); if ( empty( $cedula ) ) return $validation_result; $entries = GFAPI::get_entries( 3, array( 'status' => 'active', 'payment_status' => 'Paid', ) ); foreach ( $entries as $entry ) { if ( trim( $entry['20'] ?? '' ) === trim( $cedula ) ) { $validation_result['is_valid'] = false; foreach ( $form['fields'] as &$field ) { if ( $field->id == 20 ) { $field->failed_validation = true; $field->validation_message = 'Esta cédula ya tiene una inscripción confirmada en el AFI Summit 2026.'; } } break; } } $validation_result['form'] = $form; return $validation_result; } // ------------------------------------------------------- // CONFIRMACION: formulario POST hacia ePayco Standard Checkout // ------------------------------------------------------- add_filter( 'gform_confirmation', 'afidro_redirigir_epayco', 10, 4 ); function afidro_redirigir_epayco( $confirmation, $form, $entry, $ajax ) { if ( (int) $form['id'] !== AFIDRO_FORM_ID ) { return $confirmation; } $nombre = trim( rgar( $entry, F_NOMBRE . '.3' ) . ' ' . rgar( $entry, F_NOMBRE . '.6' ) ); if ( empty( $nombre ) ) { $nombre = rgar( $entry, F_NOMBRE ); } $email = rgar( $entry, F_EMAIL ); $telefono = rgar( $entry, F_TELEFONO ); $ciudad = rgar( $entry, F_CIUDAD ); $cantidad = (int) rgar( $entry, F_CANTIDAD ); if ( $cantidad < 1 ) { $cantidad = 1; } if ( $cantidad > 20 ) { $cantidad = 20; } $base = AFIDRO_PRECIO * $cantidad; // Aplicar código promocional si existe $codigo_promo = strtoupper( trim( rgar( $entry, '14' ) ) ); if ( ! empty( $codigo_promo ) && function_exists( 'afidro_get_codigos_promocionales' ) ) { $codigos = afidro_get_codigos_promocionales(); if ( isset( $codigos[ $codigo_promo ] ) ) { $usado = get_option( 'afidro_codigo_usado_' . md5( $codigo_promo ), false ); if ( ! $usado ) { // Protección contra race condition con lock temporal $lock_key = 'afidro_codigo_lock_' . md5( $codigo_promo ); if ( get_transient( $lock_key ) ) { return '
El código está siendo procesado. Por favor intenta de nuevo en unos segundos.
'; } set_transient( $lock_key, 1, 30 ); $descuento_pct = $codigos[ $codigo_promo ]; // Bloquear más de 1 entrada para códigos INV (100%) if ( $descuento_pct === 100 && $cantidad > 1 ) { return 'Los códigos de cortesía son válidos para 1 entrada únicamente. Por favor regresa y selecciona 1 entrada.
'; } $base = round( $base * ( 1 - $descuento_pct / 100 ) ); } } } // Aplicar descuento por volumen si no hay código promocional if ( empty( $codigo_promo ) && function_exists( 'afidro_descuento_por_volumen' ) ) { $descuento_vol = afidro_descuento_por_volumen( $cantidad ); if ( $descuento_vol > 0 ) { $base = round( $base * ( 1 - $descuento_vol / 100 ) ); } } $iva = round( $base * AFIDRO_IVA_PCT ); $total = $base + $iva; // Si el total es 0 (código 100%), confirmar sin pasar por ePayco if ( (int) $total === 0 ) { GFAPI::update_entry_property( $entry['id'], 'payment_status', 'Paid' ); GFAPI::update_entry_property( $entry['id'], 'payment_amount', 0 ); GFAPI::update_entry_property( $entry['id'], 'payment_date', current_time( 'mysql' ) ); gform_update_meta( $entry['id'], 'epayco_transaction_id', 'INV-' . $entry['id'] ); gform_update_meta( $entry['id'], 'epayco_estado', 'Aceptada' ); gform_update_meta( $entry['id'], 'epayco_cantidad', $cantidad ); $codigo_promo_inv = strtoupper( trim( rgar( $entry, '14' ) ) ); update_option( 'afidro_codigo_usado_' . md5( $codigo_promo_inv ), array( 'entry_id' => $entry['id'], 'fecha' => current_time( 'mysql' ), 'email' => rgar( $entry, '5' ), ) ); afidro_email_inscrito( $entry['id'], 'INV-' . $entry['id'], 0 ); afidro_email_contabilidad( $entry['id'], 'INV-' . $entry['id'], 0, 'Aceptada' ); $url = home_url( '/afisummit/confirmacion-pago/' ); return ''; } $concepto = $cantidad === 1 ? 'Inscripcion individual AFI Summit 2026' : 'Inscripcion grupal AFI Summit 2026 x' . $cantidad; $ref = 'AFI2026-' . $entry['id'] . '-' . time(); gform_update_meta( $entry['id'], 'epayco_ref', $ref ); gform_update_meta( $entry['id'], 'epayco_cantidad', $cantidad ); gform_update_meta( $entry['id'], 'epayco_total', $total ); // Firma SHA256 con parametros ePayco Standard $firma_string = AFIDRO_CLIENTE_ID . '^' . AFIDRO_P_KEY . '^' . $ref . '^' . number_format( $total, 2, '.', '' ) . '^' . 'COP'; $firma = md5( $firma_string ); $params = array( 'p_cust_id_cliente' => AFIDRO_CLIENTE_ID, 'p_key' => AFIDRO_P_KEY, 'p_id_invoice' => $ref, 'p_description' => $concepto, 'p_currency_code' => 'COP', 'p_amount' => number_format( $total, 2, '.', '' ), 'p_tax' => number_format( $iva, 2, '.', '' ), 'p_amount_base' => number_format( $base, 2, '.', '' ), 'p_test_request' => AFIDRO_TEST ? 'TRUE' : 'FALSE', 'p_url_response' => home_url( '/afisummit/confirmacion-pago/' ), 'p_url_confirmation' => home_url( '/wp-json/afidro/v1/epayco-webhook/' ), 'p_signature' => $firma, 'p_billing_name' => rgar( $entry, F_NOM_FAC ), 'p_billing_address' => rgar( $entry, F_DIR ), 'p_billing_town' => $ciudad, 'p_billing_country' => 'CO', 'p_billing_email' => rgar( $entry, F_EMAIL_FAC ), 'p_billing_document' => rgar( $entry, F_NIT ), 'p_billing_phone' => $telefono, 'p_extra1' => $nombre, 'p_extra2' => $email, 'p_extra3' => $cantidad, ); $html = 'Redirigiendo al portal de pagos...
'; $html .= 'Por favor espera un momento.
'; $html .= 'Hola ' . esc_html( $nombre ) . ',
'; $cuerpo .= 'Tu inscripcion al AFI Summit 2026 ha sido confirmada.
'; $cuerpo .= '📅 Cóctel de apertura: 16 de septiembre de 2026 · 5:30 PM – 8:30 PM
Incluye ceremonia de Reconocimiento al Periodismo en Salud
📅 Jornada principal: 17 de septiembre de 2026 · 8:00 AM – 5:00 PM
'; $cuerpo .= '📍 Lugar: Hall 74, Calle 74 #14-25, Bogotá
'; $cuerpo .= 'Entradas: ' . $cantidad . '
'; $cuerpo .= 'Valor pagado: ' . $valor . ' COP
'; $cuerpo .= 'Referencia: ' . esc_html( $transaccion ) . '
'; $cuerpo .= 'Importante: Debes registrar los datos de ' . $adicionales . ' asistente(s) adicional(es).
'; $cuerpo .= ''; $cuerpo .= 'Enlace válido para un solo uso. Referencia: ' . esc_html( $transaccion ) . '
'; $cuerpo .= 'Consultas: eventos@afidro.org
'; $cuerpo .= '| Nombre / Razon social | ' . esc_html( $nom_fac ) . ' |
| NIT / Cedula | ' . esc_html( $nit ) . ' |
| Direccion | ' . esc_html( $dir ) . ' |
| Ciudad | ' . esc_html( $ciudad ) . ' |
| Email factura | ' . esc_html( $em_fac ) . ' |
| Concepto | ' . esc_html( $concepto ) . ' |
| Referencia ePayco | ' . esc_html( $transaccion ) . ' |
| Estado | ' . esc_html( $estado ) . ' |
| Entradas | ' . $cantidad . ' |
| Valor base sin IVA | ' . $base_fmt . ' COP |
| IVA 19% | ' . $iva_fmt . ' COP |
| TOTAL PAGADO | ' . $total_fmt . ' COP |
| Nombre | ' . esc_html( $nombre ) . ' |
| Empresa | ' . esc_html( $empresa ) . ' |
| Cargo | ' . esc_html( $cargo ) . ' |
| ' . esc_html( $email ) . ' | |
| Telefono | ' . esc_html( $telefono ) . ' |